package cms.web.util;

import org.apache.commons.lang3.ObjectUtils;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.web.context.request.RequestAttributes;
import org.springframework.web.context.request.RequestContextHolder;

import javax.servlet.ServletContext;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;

/**
 * <p>文件名称: HttpServletUtils.java</p>
 * <p>文件描述: HttpServlet工具类.</p>
 * @author  Wuqingming
 */

public class HttpServletUtils extends ServletUtils {
    private static final Logger logger = LoggerFactory.getLogger(HttpServletUtils.class);
    /** 默认字符编码 */
    public static final String DEFAULT_ENCODING = "UTF-8";

    /**
     * 获取session信息
     * @param request  http请求对象
     * @return
     */
    public static HttpSession getSession(HttpServletRequest request) {
        return request.getSession();
    }

    /**
     * 获取servlet上下文
     * @param request  http请求对象
     * @return
     */
    public static ServletContext getServletContext(HttpServletRequest request) {
        return request.getSession().getServletContext();
    }

    /**
     * 获取绝对地址路径
     * @param request  http请求对象
     * @param path  相对路径
     * @return
     */
    public static String getRealPath(HttpServletRequest request, String path) {
        return getServletContext(request).getRealPath(path);
    }

    /**
     * 从http请求对象中获取请求参数并构建为Map对象
     * @param request  http请求对象
     * @return
     */
    @SuppressWarnings({ "rawtypes" })
    public static Map<String, Object> getParameterMap(HttpServletRequest request){
        Map<String, Object> result 	= new HashMap<String, Object>();
        Iterator<?> iterator = request.getParameterMap().entrySet().iterator();
        while (iterator.hasNext()) {
            Map.Entry entry = (Map.Entry) iterator.next();
            String key 		= entry.getKey().toString();
            Object value	= entry.getValue();
            result.put(key,  value);
        }
        return result;
    }

    public static Map<String, Object> getHeaderMap(HttpServletRequest request){
        Map<String, Object> result 	= new HashMap<String, Object>();
        Enumeration enumeration = request.getHeaderNames();
        while (enumeration.hasMoreElements()) {
            String headerName = ObjectUtils.toString(enumeration.nextElement(), "");
            result.put(headerName, request.getHeader(headerName));
        }
        return result;
    }

    /**
     * 判断请求是否为ajax请求
     * @param request
     * @return
     */
    public static boolean isAjaxRequest(final HttpServletRequest request) {
        String key = "Accept";
        String ajaxRequest = request.getHeader(key);
        if (StringUtils.isEmpty(ajaxRequest)) {
            ajaxRequest = request.getParameter(key);
        }
        if (StringUtils.isNotBlank(ajaxRequest)) {
            return ajaxRequest.contains("application/json");
        }
        return false;
    }


    /**
     * 往response流中写入字符串
     * @param response
     * @param str
     */
    public static void outString(HttpServletResponse response, String str) {
        if(response == null) return;
        PrintWriter out = null;
        try {
            response.setContentType("text/html;charset=utf-8");
            out = response.getWriter();
            out.write(str);
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            if (out != null) {
                out.flush();
                out.close();
            }
        }
    }

    /**
     * 检测发起请求的客户端浏览器信息
     * @param request  http请求对象
     * @return
     */
    public static BrowserInfo detectBrowser(final HttpServletRequest request) {
        return new BrowserInfo(request);
    }

    public static void outJson(HttpServletResponse response, Object obj) {
        String jsonString = JsonUtils.toJson(obj);
        outString(response, jsonString);
    }

    public static RequestAttributes getRequestAttributesSafely(){
        RequestAttributes requestAttributes = null;
        try{
            requestAttributes = RequestContextHolder.currentRequestAttributes();
        }catch (IllegalStateException e){
            requestAttributes = new NonWebRequestAttributes();
        }
        return requestAttributes;
    }

    /**
     * 浏览器信息
     * @author Wuqingming
     *
     */
    public static class BrowserInfo {
        private String browser;

        private String version;

        public BrowserInfo(final HttpServletRequest request) {
            final String browserType = request.getHeader("User-Agent").toLowerCase();
            if (browserType != null) {
                if ((browserType.indexOf("msie") != -1)) {
                    browser = "ie";
                    final String tempStr = browserType.substring(browserType.indexOf("msie"),
                            browserType.length());
                    version = tempStr.substring(4, tempStr.indexOf(";"));
                } else if (browserType.indexOf("firefox") != -1) {
                    browser = "firefox";
                } else if (browserType.indexOf("opera") != -1) {
                    browser = "opera";
                } else if (browserType.indexOf("safari") != -1) {
                    browser = "safari";
                }
            }
        }

        /**
         * 是否为IE浏览器
         * @return
         */
        public boolean isIE() {
            return browser != null && browser.equals("ie");
        }

        /**
         * 是否为火狐浏览器
         * @return
         */
        public boolean isFirefox() {
            return browser != null && browser.equals("firefox");
        }

        /**
         * 获取版本号
         * @return
         */
        public String getVersion() {
            return version;
        }

        public String createPostfix(final String filename) {
            if (isIE()) {
                return filename;
            } else {
                final int dotIndex = filename.lastIndexOf(".");
                final boolean dot = dotIndex != -1;
                final String s1 = dot ? filename.substring(0, dotIndex) : filename;
                final String s2 = dot ? filename.substring(dotIndex) : "";
                if (isFirefox()) {
                    return s1 + "_ff" + s2;
                }
            }
            return null;
        }

    }

}